package com.dcits.business.server.linux.parse;

import java.math.RoundingMode;
import java.text.DecimalFormat;
import java.util.Map;

import com.dcits.business.server.linux.LinuxMonitoringInfo;
import com.dcits.business.server.linux.LinuxServer;
import com.dcits.tool.StringUtils;

/**
 * 
 * 不同类型的linux类型有不同的解析工具,新的类型继承此类即可
 * @author xuwangcheng
 * @version 2018.3.21
 *
 */
public abstract class ParseInfo {
	
	private static LinuxParseInfo linuxParseUtil = new LinuxParseInfo();
	private static HPUXParseInfo hpuxParseUtil = new HPUXParseInfo();
	private static SUNOSParseInfo sunosParseUtil = new SUNOSParseInfo();
	
	protected static final String GET_INFO_FAILED_MSG = "0";
	
	
	/**
	 * 解析vmstat返回的信息<br>
	 * 不同类型的主机可能都可以执行vmstat,但是返回的格式可能不相同<br>
	 * 不再使用长连接获取信息
	 * @param info
	 * @param realTimeInfo
	 * @return null
	 */	
	public void parseVmstatInfo(String info, LinuxMonitoringInfo monitoringInfo, String uname, Long totalMem){
		
		if (StringUtils.isEmpty(info)) {
			monitoringInfo.setFreeCpu(GET_INFO_FAILED_MSG);
			monitoringInfo.setFreeMem(GET_INFO_FAILED_MSG);	
			return;
		}
		
		String[] infos = info.trim().split("(\\s)+");
		
		DecimalFormat formater = new DecimalFormat();  
		formater.setMaximumFractionDigits(1);  
		formater.setRoundingMode(RoundingMode.UP); 
		Double freeMem = 0.0;
		String idle = "";		
		
		if (uname.matches(LinuxServer.SUNOS_TYPE + "|" + LinuxServer.HPUX_TYPE)) {
			freeMem = Double.parseDouble(infos[4]);
			idle = infos[infos.length - 1];
			monitoringInfo.setIoWait("");
		} else {
			freeMem = ((Double.valueOf(infos[3]) 
					+ Double.valueOf(infos[4]) 
					+ Double.valueOf(infos[5])));
			idle = infos[infos.length - 3];
			monitoringInfo.setIoWait(infos[infos.length - 2]);
		}		
		monitoringInfo.setFreeCpu(idle);
		monitoringInfo.setFreeMem(formater.format((freeMem / Double.parseDouble(String.valueOf(totalMem))) * 100));		
	};
	
	
	/**
	 * 解析返回的tcp端口信息<br>
	 * @param info
	 * @return
	 */
	public void parseTcpInfo(String info, LinuxMonitoringInfo monitoringInfo) {
		
		Map<String, Object> map = monitoringInfo.getTcpInfo();	
		map.put(LinuxMonitoringInfo.TCP_CLOSE_WAIT, GET_INFO_FAILED_MSG);
		map.put(LinuxMonitoringInfo.TCP_ESTABLISHED, GET_INFO_FAILED_MSG);
		map.put(LinuxMonitoringInfo.TCP_LISTEN, GET_INFO_FAILED_MSG);
		map.put(LinuxMonitoringInfo.TCP_TIME_WAIT, GET_INFO_FAILED_MSG);
		
		if (info != null && !info.isEmpty()) {
			String[] strs = info.split(",");
			String[] ss = null;
			for (String s:strs) {
				ss = s.trim().split("\\s+");
				map.put(ss[1], ss[0]);
			}
						
		}
	};
	
	/**
	 * 解析返回的网络带宽信息<br>
	 * @param info
	 * @param realTimeInfo
	 */
	public void parseNetworkInfo(String info, LinuxMonitoringInfo monitoringInfo) {
		
	};
	
	/**
	 * 解析返回的磁盘空间信息<br>
	 * @param info
	 * @param realTimeInfo
	 */
	public void parseDiskInfo(String info, LinuxMonitoringInfo monitoringInfo) {		
		Map<String, Object> map = monitoringInfo.getDiskInfo();
		map.put(LinuxMonitoringInfo.DISK_ROOT, GET_INFO_FAILED_MSG);
		map.put(LinuxMonitoringInfo.DISK_USER, GET_INFO_FAILED_MSG);
		if (info != null && !info.isEmpty()) {
			String[] strs = info.split(",");
			String[] ss = null;
			
			ss = strs[0].trim().split("\\s+");
			String percent = ss[4].substring(0, ss[4].length() - 1);
			
			if (!ss[4].contains("%")) {
				percent = ss[3].substring(0, ss[3].length() - 1);
			} 
			
			map.put(LinuxMonitoringInfo.DISK_ROOT, percent);
			
			if (strs.length > 1) {
				ss = strs[1].trim().split("\\s+");
				
				String percent2 = ss[4].substring(0, ss[4].length() - 1);
				
				if (!ss[4].contains("%")) {
					percent2 = ss[3].substring(0, ss[3].length() - 1);
				}
				
				map.put(LinuxMonitoringInfo.DISK_USER, percent2);
			}

		}
	};
	/**
	 * 解析当前主机挂载的磁盘设备信息
	 * @param info
	 * @param monitoringInfo
	 *  xvda
		xvdc
		xvdb
		dm-0
		dm-1
		dm-2
		dm-3
		dm-4
		dm-5
		dm-6
		dm-7
		dm-8
		xvdd
	 */
	public abstract void parseMountDevice(String info, LinuxMonitoringInfo monitoringInfo);
	/**
	 * 解析磁盘IO读写
	 * @param info
	 * @param monitoringInfo
	 * 	读MB	  写MB
	 *  0.00 0.00
		0.00 0.00
		0.00 0.00
		0.00 0.00
		0.00 0.00
		0.00 0.00
		0.00 0.00
		0.00 0.00
		0.00 0.00
		0.00 0.00
		0.00 0.00
		0.00 0.00
		0.00 0.00
	 */
	public abstract void parseDeviceIOInfo(String info, LinuxMonitoringInfo monitoringInfo);
	
	/**
	 * 获取uname获取指定类型的解析实例
	 * @param uname
	 * @return
	 */
	public static ParseInfo getParseUtilInstance(String uname) {
		switch (uname) {
		case LinuxServer.LINUX_TYPE:
			return linuxParseUtil;
		case LinuxServer.HPUX_TYPE:
			return hpuxParseUtil;
		case LinuxServer.SUNOS_TYPE:
			return sunosParseUtil;
		default:
			return linuxParseUtil;
		}
	}
}
